package grape.auth.rest.auth2.wxmp;

import grape.auth.rest.auth2.Auth2Mapper;
import grape.base.rest.client.user.UserClient;
import grape.base.service.user.dto.UserThirdCreateParam;
import grape.base.service.user.po.User;
import grape.common.service.common.dictenums.PublicDictEnums;
import grape.wx.rest.client.user.MpUserClient;
import grape.wx.service.mp.user.po.MpUser;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.authentication.dao.DaoAuthenticationProvider;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UsernameNotFoundException;

/**
 * 自定义一个provide目前主要为了微信登录
 * Created by yangwei
 * Created at 2020/7/28 13:37
 */
public class WxMpCodeAuthenticationProvider extends DaoAuthenticationProvider {
    @Autowired
    private MpUserClient mpUserClient;
    @Autowired
    private UserClient userClient;

    @Autowired
    private Auth2Mapper auth2Mapper;

    @Override
    public boolean supports(Class<?> authentication) {
        return (WxMpCodeAuthenticationToken.class
                .isAssignableFrom(authentication));
    }

    @Override
    public Authentication authenticate(Authentication authentication) throws AuthenticationException {
        String[] pri = authentication.getPrincipal().toString().split(" ");
        if (pri.length == 1) {
            throw new UsernameNotFoundException("principal=["+ authentication.getPrincipal().toString() +"],未获取到用户id,微信登录用户名格式不正确，请确认用户名是appid和登录/用户类型编码以空格分隔");
        }
        // 确保微信用户已接收完毕
        MpUser mpUser = mpUserClient.oauth2getUserInfo(pri[0], authentication.getCredentials().toString());
        if (mpUser == null) {
            throw  new UsernameNotFoundException("principal=["+ authentication.getPrincipal() +"],credentials=["+ authentication.getCredentials() +"],未获取到用户");
        }
        // 确保第三方用户已接收完毕
        UserThirdCreateParam createParam = auth2Mapper.map(mpUser);
        createParam.setCategoryDictCode(pri[1]);

        User user = userClient.saveOrUpdateFrontUser(createParam);
        if (user == null) {
            throw  new UsernameNotFoundException("principal=["+ authentication.getPrincipal() +"],credentials=["+ authentication.getCredentials() +"],未获取到用户");
        }
        Authentication userAuth = new WxMpCodeAuthenticationToken(createParam.getOpenId(), "N/A");

        return super.authenticate(userAuth);
    }

    @Override
    protected void additionalAuthenticationChecks(UserDetails userDetails, UsernamePasswordAuthenticationToken authentication) throws AuthenticationException {
        // 不需要额外验证 主要是去除密码验证
    }
}
